bitkeeper revision 1.1159.1.429 (419b24f2Eb_QhjT-WzlSl5_8eiYX7w)
authorcl349@freefall.cl.cam.ac.uk <cl349@freefall.cl.cam.ac.uk>
Wed, 17 Nov 2004 10:16:18 +0000 (10:16 +0000)
committercl349@freefall.cl.cam.ac.uk <cl349@freefall.cl.cam.ac.uk>
Wed, 17 Nov 2004 10:16:18 +0000 (10:16 +0000)
sync w/ head.

1  2 
linux-2.6.9-xen-sparse/arch/xen/i386/kernel/entry.S
linux-2.6.9-xen-sparse/arch/xen/i386/kernel/setup.c
linux-2.6.9-xen-sparse/arch/xen/i386/kernel/traps.c
linux-2.6.9-xen-sparse/arch/xen/kernel/evtchn.c
linux-2.6.9-xen-sparse/drivers/xen/evtchn/evtchn.c
linux-2.6.9-xen-sparse/include/asm-xen/asm-i386/pgtable-2level.h
xen/arch/x86/memory.c
xen/common/keyhandler.c

index c59d6bfe7c5b71673b35390bb80c2933719ec6ea,9b2fa628e1d51bbd755ba4fc689a4daf888af181..a71ddda1b72a04ebc9fa920ac06cb5f93b4c3000
@@@ -1072,70 -1070,3 +1070,15 @@@ void __init trap_init(void
         */
        cpu_init();
  }
- /*
-  * install_safe_pf_handler / install_normal_pf_handler:
-  * 
-  * These are used within the failsafe_callback handler in entry.S to avoid
-  * taking a full page fault when reloading FS and GS. This is because FS and 
-  * GS could be invalid at pretty much any point while Xen Linux executes (we 
-  * don't set them to safe values on entry to the kernel). At *any* point Xen 
-  * may be entered due to a hardware interrupt --- on exit from Xen an invalid 
-  * FS/GS will cause our failsafe_callback to be executed. This could occur, 
-  * for example, while the mmmu_update_queue is in an inconsistent state. This
-  * is disastrous because the normal page-fault handler touches the update
-  * queue!
-  * 
-  * Fortunately, within the failsafe handler it is safe to force DS/ES/FS/GS
-  * to zero if they cannot be reloaded -- at this point executing a normal
-  * page fault would not change this effect. The safe page-fault handler
-  * ensures this end result (blow away the selector value) without the dangers
-  * of the normal page-fault handler.
-  * 
-  * NB. Perhaps this can all go away after we have implemented writable
-  * page tables. :-)
-  */
- asmlinkage void do_safe_page_fault(struct pt_regs *regs, 
-                                    unsigned long error_code,
-                                    unsigned long address)
- {
-       if (!fixup_exception(regs))
-               die("Unhandleable 'safe' page fault!", regs, error_code);
- }
- unsigned long install_safe_pf_handler(void)
- {
-       static trap_info_t safe_pf[] = { 
-               { 14, 0, __KERNEL_CS, (unsigned long)safe_page_fault },
-               {  0, 0,           0, 0                              }
-       };
-       unsigned long flags;
-       local_irq_save(flags);
-       HYPERVISOR_set_trap_table(safe_pf);
-       return flags; /* This is returned in %%eax */
- }
- __attribute__((regparm(3))) /* This function take its arg in %%eax */
- void install_normal_pf_handler(unsigned long flags)
- {
-       static trap_info_t normal_pf[] = { 
-               { 14, 0, __KERNEL_CS, (unsigned long)page_fault },
-               {  0, 0,           0, 0                         }
-       };
-       HYPERVISOR_set_trap_table(normal_pf);
-       local_irq_restore(flags);
- }
 +
 +int smp_trap_init(trap_info_t *trap_ctxt)
 +{
 +      trap_info_t *t = trap_table;
 +
 +      for (t = trap_table; t->address; t++) {
 +              trap_ctxt[t->vector].flags = t->flags;
 +              trap_ctxt[t->vector].cs = t->cs;
 +              trap_ctxt[t->vector].address = t->address;
 +      }
 +      return SYSCALL_VECTOR;
 +}
index e125cc4b08b8fe55971e2e67e0f7eb53b4192ffd,9648518ae812053e74b6ca196b1d328c4d017048..fa363ede5b8f5d3fd6a35853e2db9f99c6301069
@@@ -551,15 -466,14 +551,17 @@@ void irq_resume(void
  void __init init_IRQ(void)
  {
      int i;
 +    int cpu;
  
+     irq_ctx_init(0);
      spin_lock_init(&irq_mapping_update_lock);
  
 -    /* No VIRQ -> IRQ mappings. */
 -    for ( i = 0; i < NR_VIRQS; i++ )
 -        virq_to_irq[i] = -1;
 +    for ( cpu = 0; cpu < NR_CPUS; cpu++ ) {
 +      /* No VIRQ -> IRQ mappings. */
 +      for ( i = 0; i < NR_VIRQS; i++ )
 +          per_cpu(virq_to_irq, cpu)[i] = -1;
 +    }
  
      /* No event-channel -> IRQ mappings. */
      for ( i = 0; i < NR_EVENT_CHANNELS; i++ )
index c7a40f936abe6c5f4413e328d1f008ff53cef512,7000c5dbe88be95bce03c23d330744376179328c..dcab5348aed94d9a1cd4d10685568b6ff73bdda1
@@@ -23,24 -23,10 +23,22 @@@ static inline int pgd_present(pgd_t pgd
   * within a page table are directly modified.  Thus, the following
   * hook is made available.
   */
- #ifdef CONFIG_XEN_WRITABLE_PAGETABLES
+ #define set_pte_batched(pteptr, pteval) \
+ queue_l1_entry_update(pteptr, (pteval).pte_low)
++
 +#ifdef CONFIG_SMP
 +#define set_pte(pteptr, pteval) xen_l1_entry_update(pteptr, (pteval).pte_low)
 +#if 0
 +do { \
 +  (*(pteptr) = pteval); \
 +  HYPERVISOR_xen_version(0); \
 +} while (0)
 +#endif
 +#define set_pte_atomic(pteptr, pteval) set_pte(pteptr, pteval)
 +#else
  #define set_pte(pteptr, pteval) (*(pteptr) = pteval)
- #define set_pte_atomic(pteptr, pteval) (*(pteptr) = pteval)
- #else
- #define set_pte(pteptr, pteval) xen_l1_entry_update(pteptr, (pteval).pte_low)
- #define set_pte_atomic(pteptr, pteval) xen_l1_entry_update(pteptr, (pteval).pte_low)
- #endif
+ #define set_pte_atomic(pteptr, pteval) set_pte(pteptr,pteval)
 +#endif
  /*
   * (pmds are folded into pgds so this doesn't get actually called,
   * but the define is needed for a generic inline function.)
index 307c532d441f55bd715dc486dbff29f5f2eab66e,fafbb404918bc3d338dc55c03c0f119ab78d51e4..0e295e6df4c31c92e64b4aab07ac8fe4ef694e6f
@@@ -1590,10 -1577,9 +1590,10 @@@ void ptwr_flush(const int which
  {
      unsigned long  sstat, spte, pte, *ptep, l1va;
      l1_pgentry_t  *sl1e = NULL, *pl1e, ol1e, nl1e;
-     l2_pgentry_t  *pl2e, nl2e;
+     l2_pgentry_t  *pl2e;
      int            i, cpu = smp_processor_id();
 -    struct domain *d = current;
 +    struct exec_domain *ed = current;
 +    struct domain *d = ed->domain;
  
      l1va = ptwr_info[cpu].ptinfo[which].l1va;
      ptep = (unsigned long *)&linear_pg_table[l1va>>PAGE_SHIFT];
       * STEP 3. Reattach the L1 p.t. page into the current address space.
       */
  
 -    if ( (which == PTWR_PT_ACTIVE) && likely(!d->mm.shadow_mode) )
 +    if ( (which == PTWR_PT_ACTIVE) && likely(!ed->mm.shadow_mode) )
      {
          pl2e = &linear_l2_table[ptwr_info[cpu].ptinfo[which].l2_idx];
-         nl2e = mk_l2_pgentry(l2_pgentry_val(*pl2e) | _PAGE_PRESENT);
-         update_l2e(pl2e, *pl2e, nl2e);
+         *pl2e = mk_l2_pgentry(l2_pgentry_val(*pl2e) | _PAGE_PRESENT); 
      }
  
      /*
  /* Write page fault handler: check if guest is trying to modify a PTE. */
  int ptwr_do_page_fault(unsigned long addr)
  {
-     unsigned long    pte, pfn;
+     unsigned long    pte, pfn, l2e;
      struct pfn_info *page;
-     l2_pgentry_t    *pl2e, nl2e;
+     l2_pgentry_t    *pl2e;
      int              which, cpu = smp_processor_id();
      u32              l2_idx;
 +    struct domain   *d = current->domain;
  
 +    LOCK_BIGLOCK(d);
      /*
       * Attempt to read the PTE that maps the VA being accessed. By checking for
       * PDE validity in the L2 we avoid many expensive fixups in __get_user().
      /* Get the L2 index at which this L1 p.t. is always mapped. */
      l2_idx = page->u.inuse.type_info & PGT_va_mask;
      if ( unlikely(l2_idx >= PGT_va_unknown) )
 +    {
 +        UNLOCK_BIGLOCK(d);
          domain_crash(); /* Urk! This L1 is mapped in multiple L2 slots! */
 +    }
      l2_idx >>= PGT_va_shift;
-         
+     if ( l2_idx == (addr >> L2_PAGETABLE_SHIFT) )
+     {
+         MEM_LOG("PTWR failure! Pagetable maps itself at %08lx\n", addr);
+         domain_crash();
+     }
      /*
       * Is the L1 p.t. mapped into the current address space? If so we call it
       * an ACTIVE p.t., otherwise it is INACTIVE.
      /* For safety, disconnect the L1 p.t. page from current space. */
      if ( (which == PTWR_PT_ACTIVE) && likely(!current->mm.shadow_mode) )
      {
-         nl2e = mk_l2_pgentry(l2_pgentry_val(*pl2e) & ~_PAGE_PRESENT);
-         update_l2e(pl2e, *pl2e, nl2e);
+         *pl2e = mk_l2_pgentry(l2e & ~_PAGE_PRESENT);
 +#if 0
          flush_tlb(); /* XXX Multi-CPU guests? */
 +#else
 +        flush_tlb_all();
 +#endif
      }
      
      /* Temporarily map the L1 page, and make a copy of it. */
Simple merge